package cn.hy.service;


import cn.hutool.core.util.IdUtil;
import cn.hy.dto.UserDto;
import cn.hy.mapper.SecKillGoodsMapper;
import cn.hy.util.MD5Utils;
import cn.hy.vo.GoodsVo;
import cn.hy.vo.SecKillGoodsVo;
import cn.hy.vo.SecKillOrderVo;
import org.apache.commons.lang3.StringUtils;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.concurrent.TimeUnit;

import static cn.hy.redis.key.SecKillKey.GOODS_OVER;
import static cn.hy.redis.key.SecKillKey.SK_PATH;

/**
 * 核心服务
 */
@Service
public class SecKillServiceImpl implements SecKillService {

    @Resource
    private StringRedisTemplate stringRedisTemplate;

    @Resource
    private SecKillGoodsMapper secKillGoodsMapper;

    @Resource
    private OrderService orderService;

    @Override
    public void secKill(UserDto userDto, GoodsVo goodsVo) {
        //减库存 下订单 写入秒杀订单
        int success = secKillGoodsMapper.reduceStock(goodsVo.getId());
        if (success > 0) {
            orderService.createOrder(userDto, goodsVo);
        } else {
            //如果库存不存在则内存标记为true
            stringRedisTemplate.opsForValue().set(GOODS_OVER.getKey(String.valueOf(goodsVo.getId())), "1", 600, TimeUnit.SECONDS);
        }
    }

    @Override
    public boolean checkPath(String nickname, Long goodsId, String path) {
        if (StringUtils.isEmpty(nickname) || StringUtils.isEmpty(path)) {
            return false;
        }
        String pathOld = stringRedisTemplate.opsForValue().get(SK_PATH.getKey(nickname, String.valueOf(goodsId)));
        return path.equals(pathOld);
    }

    @Override
    public Long getSecKillResult(Long userId, Long goodsId) {
        SecKillOrderVo order = orderService.getSecKillOrderByUserIdGoodsId(userId, goodsId);
        if (order != null) {//秒杀成功
            return order.getOrderId();
        } else {
            String isOver = stringRedisTemplate.opsForValue().get(GOODS_OVER.getKey(String.valueOf(goodsId)));
            if (StringUtils.isEmpty(isOver)) {
                return 0L;
            } else {
                return Long.valueOf(isOver);
            }
        }
    }

    @Override
    public boolean checkVerifyCode(Long userId, Long goodsId, Integer verifyCode) {
        return verifyCode.equals(10);
    }

    @Override
    public String createSecKillPath(String nickname, Long goodsId) {
        if (nickname == null || goodsId <= 0) {
            return null;
        }
        String str = MD5Utils.md5(IdUtil.fastSimpleUUID() + "123456");
        stringRedisTemplate.opsForValue().set(SK_PATH.getKey(nickname, String.valueOf(goodsId)),
                str, SK_PATH.expireSeconds(), TimeUnit.SECONDS);
        return str;
    }


}
